import { message } from 'antd';

import store from '@/reducers';
import { userActions } from '@/reducers/user';

import { query2search } from './common';

type ReqConfig = {
  url?: string;
  method?: 'get' | 'post';
  params?: Record<string, any>;
  headers?: Record<string, string>;
  data?: any;
  hiddenMsg?: boolean;
};
function req<T>({
  url = '',
  method = 'get',
  params = {},
  data = null,
  headers = {},
  hiddenMsg,
}: ReqConfig): Promise<T> {
  return new Promise((resolve, reject) => {
    const search = query2search(params);

    if (search) {
      url += url.indexOf('?') == -1 ? '?' + search : '&' + search;
    }

    const xhr = new XMLHttpRequest();
    xhr.open(method, url, true);
    if (!headers['Content-Type']) {
      headers['Content-Type'] = 'application/json;charset=UTF-8';
    }
    headers.token = localStorage.getItem('token') || ''
    for (const key in headers) {
      xhr.setRequestHeader(key, headers[key]);
    }
    xhr.onreadystatechange = function () {
      if (xhr.readyState === 4) {
        let data: any = xhr.responseText;
        try {
          data = JSON.parse(xhr.responseText);
        } catch (error) {
          console.error(error);
        }

        if (xhr.status >= 200 && xhr.status < 300) {
          resolve(typeof data.data == 'object' && data.data != null ? data.data : data);
        } else {
          const msg = data.message;
          if (data.code == '401') {
            store.dispatch(userActions.setState({ login: false }));
          }
          if (msg && !hiddenMsg) {
            message.error(msg);
          }
          reject(data);
        }
      }
    };
    xhr.onerror = function (e) {
      reject(e);
    };
    xhr.send(typeof data == 'object' && data !== null ? JSON.stringify(data) : data);
  });
}
const get = <T = any>(url: string, params: ReqConfig['params'] = {}, config: ReqConfig = {}) => {
  return req<T>({ url, method: 'get', params, ...config });
};
const post = <T = any>(url: string, data: ReqConfig['data'] = {}, config: ReqConfig = {}) => {
  return req<T>({ url, method: 'post', data, ...config });
};
export default {
  get,
  post,
};
